import 'dart:convert';

import 'package:flutter/material.dart';
import 'package:fluttertoast/fluttertoast.dart';
import 'package:kxy_flutter_app/auth.dart';
import 'package:kxy_flutter_app/components/loading_widget.dart';
import 'package:kxy_flutter_app/helper/http.dart';
import 'package:kxy_flutter_app/model/const_exam_category.dart';
import 'package:kxy_flutter_app/model/exam_question.dart';
import 'package:kxy_flutter_app/view/examination/do_review_view.dart';
import 'package:line_awesome_icons/line_awesome_icons.dart';
import 'package:shared_preferences/shared_preferences.dart';

class ConstCateView extends StatefulWidget {
  final String parentId;

  ConstCateView({this.parentId = '0'});

  @override
  _ConstCateViewState createState() => _ConstCateViewState();
}

class _ConstCateViewState extends State<ConstCateView> {
  List<ConstExamCategory> cateList = new List<ConstExamCategory>();
  Future loadFuture;

  @override
  void initState() {
    super.initState();
    loadFuture = loadCateList();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Colors.white,
      appBar: AppBar(title: Text('专业提升')),
      body: FutureBuilder(
        future: loadFuture,
        builder: (BuildContext context, AsyncSnapshot snapshot) {
          if (snapshot.connectionState == ConnectionState.done) {
            return body();
          }
          return LoadingWidget();
        },
      ),
    );
  }

  Widget body() {
    return ListView(
      children: ListTile.divideTiles(
        tiles: cateList.map((e) => cateItemWidget(e)),
        color: Colors.black12,
        context: context,
      ).toList(),
    );
  }

  Widget cateItemWidget(ConstExamCategory cate) {
    return ListTile(
      contentPadding: EdgeInsets.symmetric(horizontal: 20),
      title: Text(cate.name),
      trailing: Icon(
        LineAwesomeIcons.angle_right,
        size: 16,
      ),
      onTap: () {
        if (cate.childNum > 0) {
          gotoChildCate(cate.id);
        } else {
          doExam(cate);
        }
      },
    );
  }

  Future gotoChildCate(String cateId) async {
    Navigator.push(
      context,
      MaterialPageRoute(
        builder: (cxt) => ConstCateView(parentId: cateId),
      ),
    );
  }

  Future doExam(ConstExamCategory cate) async {
    try {
      var quesList = await getQuesList(cate);
      if (quesList == null || quesList.length == 0) {
        Fluttertoast.showToast(msg: '当前考试中没有试题！');
        return;
      }

      var result = await confirmStartExam(cate, quesList);
      if (result == false) {
        return;
      }
      await Navigator.push(
        context,
        MaterialPageRoute(
          builder: (cxt) => DoReviewView(
            title: cate.name,
            quesList: quesList,
            readonly: false,
            initIndex: quesList.indexWhere((x) => x.confirmed == false),
          ),
        ),
      );
      await saveQuesList(cate, quesList);
    } catch (e) {
      Fluttertoast.showToast(msg: '获取试题失败，请联系管理员。');
    }
  }

  Future<bool> confirmStartExam(ConstExamCategory cate, List<Question> quesList) async {
    bool resetQuesList = false;
    if (quesList.indexWhere((x) => x.userAnswer != null && x.userAnswer.isNotEmpty) > -1) {
      resetQuesList = await confirmResetQuesListDialog();
      if (resetQuesList == null) {
        return false;
      }
    }

    if (resetQuesList) {
      quesList.forEach((item) {
        item.confirmed = false;
        item.userAnswer = '';
      });
    }
    return true;
  }

  Future<bool> confirmResetQuesListDialog() async {
    return await showDialog(
        context: context,
        builder: (cxt) {
          return AlertDialog(
            title: Text('提示'),
            content: Text('您要继续练习吗？'),
            actions: [
              FlatButton(
                child: Text('重新开始'),
                onPressed: () {
                  Navigator.pop(context, true);
                },
              ),
              FlatButton(
                child: Text('继续练习'),
                onPressed: () {
                  Navigator.pop(context, false);
                },
              )
            ],
          );
        });
  }

  Future<bool> saveQuesList(ConstExamCategory cate, List<Question> quesList) async {
    var quesKey = cate.id;
    var prefs = await SharedPreferences.getInstance();
    var quesListMap = jsonEncode(quesList.map((e) => e.toConstExamJson()).toList());
    var quesObj = {
      'quesCount': quesList.length,
      'cateName': cate.name,
      'quesList': quesListMap,
    };
    var jsonStr = jsonEncode(quesObj);
    return await prefs.setString(quesKey, jsonStr);
  }

  Future<List<Question>> getQuesList(ConstExamCategory cate) async {
    var quesKey = cate.id;
    var versionKey = cate.id + '-version';
    var prefs = await SharedPreferences.getInstance();

    int version = prefs.getInt(versionKey);
    if (cate.version != version) {
      await prefs.remove(quesKey);
    }

    String jsonStr;
    if (!prefs.containsKey(quesKey)) {
      jsonStr = await getQuesListFromServer(cate.id);
      await prefs.setString(quesKey, jsonStr);
      await prefs.setInt(versionKey, cate.version);
    }

    jsonStr = prefs.getString(quesKey);
    return convertToQuesList(jsonStr);
  }

  List<Question> convertToQuesList(String jsonStr) {
    if (jsonStr == null || jsonStr.isEmpty) {
      return [];
    }

    var json = jsonDecode(jsonStr);
    List<dynamic> quesMapList;
    if (json['quesList'] is String) {
      var jsonMap = jsonDecode(json['quesList']);
      quesMapList = jsonMap as List;
    } else {
      quesMapList = json['quesList'] as List;
    }

    return quesMapList.map((e) {
      return Question.fromConstExamJson(e);
    }).toList();
  }

  Future getQuesListFromServer(String cateId) async {
    var res = await Http.instance.postData('/exam-app/craftBank/quesBankFile', params: {
      'quesCateId': cateId,
    });

    if (res.statusCode == 200) {
      return res.data;
    } else {
      Fluttertoast.showToast(msg: '下载试题失败，服务器出错。');
      return '';
    }
  }

  Future loadCateList() async {
    var res = await Http.instance.post('/exam-app/craftBank/cateList', params: {
      'parentId': widget.parentId,
      'userId': Auth.instance.userId,
    });

    if (res.code == 200) {
      cateList = (res.data as List).map((e) => ConstExamCategory.fromJson(e)).toList();
    } else {
      Fluttertoast.showToast(msg: res.msg);
    }
  }
}
